import asyncio
import time
import logging

from app.core.config import settings
from app.core.database import get_db_context, update_device_status
from app.models.models import Device
from app.utils.device_cache import device_cache

logger = logging.getLogger(__name__)


class UpdateQueue:
    def __init__(self):
        self.queue = asyncio.Queue()
        self.batch_size = settings.UPDATE_QUEUE_BATCH_SIZE
        self.batch_interval = settings.UPDATE_QUEUE_BATCH_INTERVAL  # 修复：使用正确的属性名
        self.processing = False

    async def add_update(self, dev_id: str, update_data: dict):
        """添加更新到队列"""
        await self.queue.put((dev_id, update_data))

    async def process_batch(self):
        """处理批量更新"""
        while True:
            batch = []
            start_time = time.time()

            # 收集批量更新
            while len(batch) < self.batch_size and time.time() - start_time < self.batch_interval:  # 修复：使用 batch_interval
                try:
                    # 非阻塞获取更新
                    update = await asyncio.wait_for(self.queue.get(), timeout=0.1)
                    batch.append(update)
                except asyncio.TimeoutError:
                    break
                except Exception as e:
                    logger.error(f"获取更新失败: {e}")
                    await asyncio.sleep(0.1)

            if batch:
                try:
                    # 使用单个数据库会话处理整个批次
                    async with get_db_context() as db:
                        for dev_id, update_data in batch:
                            # 高效更新数据库
                            device = db.query(Device).filter(Device.dev_id == dev_id).first()
                            if device:
                                for key, value in update_data.items():
                                    setattr(device, key, value)
                        db.commit()
                        # logger.info(f"成功批量更新 {len(batch)} 台设备状态")
                except Exception as e:
                    logger.error(f"批量更新失败: {e}")
            else:
                await asyncio.sleep(1)


# 全局更新队列
update_queue = UpdateQueue()